package purchase

import (
	"LogisticsPort/model"
	"LogisticsPort/sql"
	"errors"
	"github.com/gin-gonic/gin"
	"gorm.io/gorm"
)

func sales(r *gin.RouterGroup) {
	sales := r.Group("/sales")
	{
		sales.POST(sql.RequestAdd, purchaseSalesAdd)
		sales.POST(sql.RequestUpdate, purchaseSalesUpdate)
		sales.GET(sql.RequestDelete, purchaseSalesDelete)
		sales.GET(sql.RequestList, purchaseSalesList)
		sales.GET(sql.RequestData, purchaseSalesData)
	}
}

/*
*
港口库存销售
*/
func purchaseSalesAdd(c *gin.Context) {
	sql.HttpHandle(sql.ADD, c, func(db *gorm.DB) (*gorm.DB, interface{}) {
		var bean model.PurchaseSales
		if err := c.Bind(&bean); err != nil {
			db.Error = err
			return db, nil
		}

		if err := db.Transaction(func(tx *gorm.DB) error {

			// 1、拉回入库，新增本地库存
			if bean.CustomerId == 1 {
				var inventory = model.Inventory{
					UserId:            bean.UserId,
					PurchaseProductId: bean.PurchaseProductId,
					ProductId:         bean.ProductId,
					Date:              bean.Date,
					PurchasePrice:     bean.SalesPrice,
					PurchaseNumber:    bean.SalesNumber,
					PurchaseWeight:    bean.SalesWeight,
					InventoryNumber:   bean.SalesNumber,
					InventoryWeight:   bean.SalesWeight,
					TotalAmount:       bean.TotalPrice,
					DiscountAmount:    0,
					PaymentAmount:     bean.TotalPrice,
				}
				if err := tx.Create(&inventory).Error; err != nil {
					return err
				}
				bean.InventoryId = int(inventory.ID)
			}
			// 2、修改港口库存
			if err := tx.
				Model(&model.PurchaseProduct{}).
				Where("id = ?", bean.PurchaseProductId).
				Updates(
					map[string]interface{}{
						"inventory_number": gorm.Expr("inventory_number - ?", bean.SalesNumber),
						"inventory_weight": gorm.Expr("inventory_weight - ?", bean.SalesWeight),
					}).Error; err != nil {
				return err
			}

			// 3、创建港口销售记录
			if err := tx.Create(&bean).Error; err != nil {
				return err
			}
			// 4、如果库存为零，修改出库日期
			var inventoryNumber int
			if err := tx.Model(&model.PurchaseProduct{}).
				Where("id = ?", bean.PurchaseProductId).
				Select("inventory_number").
				Scan(&inventoryNumber).Error; err != nil {
				return err
			}
			if inventoryNumber == 0 {
				if err := tx.Table("shipping_info").
					Where("purchase_product_id=?", bean.PurchaseProductId).
					Update("delivery_date", bean.Date).Error; err != nil {
					return err
				}
			}
			return nil
		}); err != nil {
			db.Error = errors.New(sql.ErrorService)
			return db, nil
		}
		return db, bean
	})
}

func purchaseSalesUpdate(c *gin.Context) {
	sql.HttpHandle(sql.UPDATE, c, func(db *gorm.DB) (*gorm.DB, interface{}) {
		var newSalesBean model.PurchaseSales
		if err := c.Bind(&newSalesBean); err != nil {
			db.Error = err
			return db, nil
		}
		var tx = db.Begin()
		//获取已销售的商品信息
		var oldSalesBean model.PurchaseSales
		err := tx.Where("id = ?", newSalesBean.ID).Find(&oldSalesBean).Error
		if err != nil {
			tx.Callback()
			db.Error = err
			return db, nil
		}
		//如果商品入库物流港，对物流港的库存进行修改
		if oldSalesBean.InventoryId != 0 {
			var currentInventory model.Inventory
			err = tx.Where("id = ?", oldSalesBean.InventoryId).Find(&currentInventory).Error

			var changeNumber = newSalesBean.SalesNumber - currentInventory.PurchaseNumber
			var changeWeight = newSalesBean.SalesWeight - currentInventory.PurchaseWeight

			/*if currentInventory.InventoryNumber < newSalesBean.SalesNumber {
				tx.Rollback()
				db.Error = errors.New("物流港库存不足，修改失败")
				return db, nil
			}*/
			if currentInventory.InventoryNumber+changeNumber < 0 || currentInventory.InventoryWeight+changeWeight < 0 {
				tx.Rollback()
				db.Error = errors.New("物流港库存不足，修改失败")
				return db, nil
			}
			var inventory = model.Inventory{
				UserId:            newSalesBean.UserId,
				PurchaseProductId: newSalesBean.PurchaseProductId,
				ProductId:         newSalesBean.ProductId,
				Date:              newSalesBean.Date,
				PurchasePrice:     newSalesBean.SalesPrice,
				PurchaseNumber:    newSalesBean.SalesNumber,
				PurchaseWeight:    newSalesBean.SalesWeight,
				InventoryNumber:   currentInventory.InventoryNumber + changeNumber,
				InventoryWeight:   currentInventory.InventoryWeight + changeWeight,
				TotalAmount:       newSalesBean.TotalPrice,
				DiscountAmount:    0,
				PaymentAmount:     newSalesBean.TotalPrice,
			}
			err = tx.Save(&inventory).Error
			if err != nil {
				tx.Rollback()
				db.Error = err
				return db, nil
			}
		}

		//根据信息对比并对港口库存进行修改
		var weight = oldSalesBean.SalesWeight - newSalesBean.SalesWeight
		var number = oldSalesBean.SalesNumber - newSalesBean.SalesNumber
		err = tx.Model(&model.PurchaseProduct{}).
			Where("id = ?", newSalesBean.PurchaseProductId).
			Updates(map[string]interface{}{
				"inventory_number": gorm.Expr("inventory_number + ?", number),
				"inventory_weight": gorm.Expr("inventory_weight + ?", weight),
			}).Error
		if err != nil {
			tx.Rollback()
			db.Error = err
			return db, nil
		}

		//修改销售记录
		err = tx.Save(&newSalesBean).Error
		if err != nil {
			tx.Callback()
			db.Error = err
			return db, nil
		}

		tx.Commit()
		return db, newSalesBean
	})
}

func purchaseSalesDelete(c *gin.Context) {
	sql.HttpHandle(sql.DELETE, c, func(db *gorm.DB) (*gorm.DB, interface{}) {
		//销售的id
		id := c.Query("id")
		var tx = db.Begin()
		//查看该商品已拉回郑州入库,如果入库郑州则不能删除
		var inventoryList []model.Inventory
		err := tx.Where("purchase_sales_id = ?", id).Find(&inventoryList).Error
		if err != nil {
			tx.Callback()
			tx.Error = err
			return tx, nil
		}
		if len(inventoryList) > 0 {
			tx.Callback()
			tx.Error = errors.New("商品已入郑州库，不可删除")
			return tx, nil
		}

		//港口销售商品的基本信息
		var purchaseSales model.PurchaseSales
		err = tx.Where("id = ?", id).First(&purchaseSales).Error
		if err != nil {
			tx.Callback()
			tx.Error = err
			return tx, nil
		}
		//如果删除商品，则修改港口库存
		err = tx.Model(&model.PurchaseProduct{}).
			Where("id = ?", purchaseSales.PurchaseProductId).
			Updates(map[string]interface{}{
				"inventory_number": gorm.Expr("inventory_number + ?", purchaseSales.SalesNumber),
				"inventory_weight": gorm.Expr("inventory_weight + ?", purchaseSales.SalesWeight),
			}).Error
		if err != nil {
			tx.Rollback()
			tx.Error = err
			return tx, nil
		}

		//删除
		err = tx.Delete(&purchaseSales).Error
		if err != nil {
			tx.Rollback()
			tx.Error = err
			return tx, nil
		}
		tx.Commit()
		return tx, nil
	})
}

func purchaseSalesList(c *gin.Context) {
	sql.HttpList(c, &[]model.PurchaseSales{}, func(db *gorm.DB) *gorm.DB {
		var purchaseProductId = c.Query("purchaseProductId")
		if purchaseProductId == "" {
			db.Error = errors.New(sql.ErrorParams)
			return db
		}
		db = db.Where("purchase_product_id = ?", purchaseProductId).
			Select("purchase_sales.*,customer.name").
			Joins("left join customer ON customer.id = purchase_sales.customer_id")
		return db
	})
}

func purchaseSalesData(c *gin.Context) {
	sql.HttpDataById(c, &model.PurchaseSales{})
}
